package org.movsim.simulator;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;

import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.ss.usermodel.WorkbookFactory;



public class B5Constants {

    public static enum B5_PSYCOLOGICAL_FACTORS {
        NEUROTICISM, EXTRAVERSION, OPENNESS, AGREEABLENESS, CONSCIENTIOUSNESS,
    }

    public static enum INPUT_FROM_ENVIRONMENT {
        DEGREE_OF_CONGESTION, DEGREE_OF_JAM, DEGREE_OF_DOWN_STREAM_SIGNAL_DISTANCE, DEGREE_OF_OVER_SPEED_AND_UNDER_SPEED, DEGREE_OF_DISTANCE_FROM_TRAILING_VEHICLE, DEGREE_OF_DISTANCE_FROM_FRONT_VEHICLE, DEGREE_OF_INSTABILITY_OF_LEFT_LANE, DEGREE_OF_INSTABILITY_OF_RIGHT_LANE,
    }
    
    public static enum DRIVER_ACTION {
        RESPECT_SPEED_LIMIT, VISIBILITY_OF_EXIT_SIGN, CONSIDER_LANE_CHANGE, SAFETY_CRITERAIA_WHILE_LANE_CHANGE, COOPRATE_WITH_ENTERING_VEHICLE_BY_CHANGING_LANE, CHECKS_IS_OWN_ACCELERATION_SAFE_WHILE_CHANGING_LANE, EFFECT_ON_ACCELERATION, DESIRED_SPEED_WHICH_EVENTUALLY_EFFECT_ACCELERATION, CONSIDER_TRAFFIC_LIGHT_IN_ACCELERATION, RESPECT_RED_LIGHT, LOOK_AHEAD_DISTANCE_INVOLVED_WITH_SIGNAL, CONSIDER_EXIT_LANE_IN_ACCELERATION, EFFECT_ON_SPEED_AND_LONGITUDNAL_POSITION, STANDSTILL_GAP, DISTANCE_BEFORE_EXIST_MUST_CHANGE_LANE, CHECK_SPACE_BEFORE_PASSING_TRAFFIC_LIGHT,
    }

    private static double[][] B5_ENVIRONMENT_VALUES = new double[INPUT_FROM_ENVIRONMENT.values().length][B5_PSYCOLOGICAL_FACTORS
            .values().length];
    
    private static double[][] B5_DRIVER_ACTION_VALUES = new double[DRIVER_ACTION.values().length][B5_PSYCOLOGICAL_FACTORS
            .values().length];

    private static final String PATHNAME_B5ENVIRONMENTVALUE = "B5AssociatiponWithEnvironment.xlsx";
    private static final String PATHNAME_B5DRIVERACTIONVALUE = "B5AssociatiponWithDriverAction.xlsx";
    private static final String PATHNAME_B5INITIAL_PSYCHOLOGICAL_STATE = "B5InitialValue.xlsx";

    static {
        try {
            populateB5EnvironmentValue();
            populateB5DriverActionValue();
        } catch (InvalidFormatException | IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

    public static void populateB5EnvironmentValue() throws InvalidFormatException, IOException {
        FileInputStream fis = new FileInputStream(new File(PATHNAME_B5ENVIRONMENTVALUE));
        Workbook book = WorkbookFactory.create(fis);
        Sheet sheet = book.getSheetAt(0);
        for (INPUT_FROM_ENVIRONMENT e : INPUT_FROM_ENVIRONMENT.values()) {
            for (B5_PSYCOLOGICAL_FACTORS p : B5_PSYCOLOGICAL_FACTORS.values()) {
                double value = sheet.getRow(e.ordinal()).getCell(p.ordinal()).getNumericCellValue();
                setB5EnvironmentValue(e, p, value);
            }
        }
    }

    public static void setB5EnvironmentValue(INPUT_FROM_ENVIRONMENT e, B5_PSYCOLOGICAL_FACTORS p, double v) {
        B5_ENVIRONMENT_VALUES[e.ordinal()][p.ordinal()] = v;
    }

    public static double getB5EnvironmentValue(INPUT_FROM_ENVIRONMENT e, B5_PSYCOLOGICAL_FACTORS p) {
        return B5_ENVIRONMENT_VALUES[e.ordinal()][p.ordinal()];
    }

    public static void printB5EnvironmentVALUES() {
        for (INPUT_FROM_ENVIRONMENT e : INPUT_FROM_ENVIRONMENT.values()) {
            for (B5_PSYCOLOGICAL_FACTORS p : B5_PSYCOLOGICAL_FACTORS.values()) {
                System.out.print(getB5EnvironmentValue(e, p) + ",");
            }
            System.out.println();
        }
    }

    public static void populateB5DriverActionValue() throws InvalidFormatException, IOException {
        FileInputStream fis = new FileInputStream(new File(PATHNAME_B5DRIVERACTIONVALUE));
        Workbook book = WorkbookFactory.create(fis);
        Sheet sheet = book.getSheetAt(0);
        for (DRIVER_ACTION e : DRIVER_ACTION.values()) {
            for (B5_PSYCOLOGICAL_FACTORS p : B5_PSYCOLOGICAL_FACTORS.values()) {
                double value = sheet.getRow(e.ordinal()).getCell(p.ordinal()).getNumericCellValue();
                setB5DriverActionValue(e, p, value);
            }
        }
    }

    public static void setB5DriverActionValue(DRIVER_ACTION e, B5_PSYCOLOGICAL_FACTORS p, double v) {
        B5_DRIVER_ACTION_VALUES[e.ordinal()][p.ordinal()] = v;
    }

    public static double getB5DriverActionValue(DRIVER_ACTION e, B5_PSYCOLOGICAL_FACTORS p) {
        return B5_DRIVER_ACTION_VALUES[e.ordinal()][p.ordinal()];
    }

    public static void printB5DriverActionVALUES() {
        for (DRIVER_ACTION e : DRIVER_ACTION.values()) {
            for (B5_PSYCOLOGICAL_FACTORS p : B5_PSYCOLOGICAL_FACTORS.values()) {
                System.out.print(getB5DriverActionValue(e, p) + ",");
            }
            System.out.println();
        }
    }

    public static double[][] readInitialPsychologicalState(){
        double[][] intialValues = new double[2][B5_PSYCOLOGICAL_FACTORS.values().length];
        try {
            FileInputStream fis = new FileInputStream(new File(PATHNAME_B5INITIAL_PSYCHOLOGICAL_STATE));
            Workbook book = WorkbookFactory.create(fis);
            Sheet sheet = book.getSheetAt(0);
            for (int i = 0; i < intialValues.length; ++i) {
                for(B5_PSYCOLOGICAL_FACTORS p: B5_PSYCOLOGICAL_FACTORS.values()){
                    intialValues[i][p.ordinal()] = sheet.getRow(i).getCell(p.ordinal()).getNumericCellValue();
                }
            }
        } catch (InvalidFormatException | IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return intialValues;
    }

}
